/**
 * Created by user on 4/22/19.
 */
import React from 'react'
import { connect } from 'react-redux'
import { singleClone, EventCenter, getSeq, getStamp, Request, setData, originData, formatSocketMsg, Data, Type, cloneObj } from '@utils/Global'
import { DmAction, QaAction, QaListAction, MainAction, LoginAction, QuestionAction } from '@act'
import liveAction from '@act/liveAction'
import { API, TEST } from '@utils/config'
import SocketManager from '@utils/SocketManager'
import GlobalTime from '@utils/GlobalTime'
import MediaManager from "@utils/MediaManager";

class SilentLogin extends React.Component {
  state = {
    canAuto: true
  }
  componentDidMount() {
    if (this.checkAudioAutoPlay()) {
      return
    }
    // this.clickLoginBtn()
    if (TEST) {
      setTimeout(() => {
        this.clickLoginBtn()
      }, 300)
    }
  }
  checkAudioAutoPlay() {
    let isSafari =  /Safari/.test(navigator.userAgent) && !/Chrome/.test(navigator.userAgent)
    this.setState({canAuto: !isSafari})
    return isSafari
  }
  initOriginData(data, code) {
    const { dispatch, loginCallback } = this.props
    setData('live', data)
    // originData['live'].info.except_time = getStamp() - 250 * 1000
    Data.user = data.user
    Data.code = code
    this.initQuestion()
    this.initDm()
    this.initSwiper()
    this.initQa()
    const info = cloneObj(originData['live'].info)
    const materials = cloneObj(originData['live'].materials)
    const teachers = cloneObj(originData['live'].teachers)
    info.token = originData['live'].token
    dispatch(MainAction.setInfoData(info))
    dispatch(MainAction.setMaterials(materials))
    dispatch(MainAction.setTeachers(teachers))
    var replayObj = null
    if (info.type !== 2) {
      const notStart = info.except_time > getStamp()
      if (notStart) {
        dispatch(MainAction.changeScreen(-2))
      } else {
        dispatch(MainAction.changeScreen(originData['live'].info.status))
      }
      dispatch(liveAction.toggleLivePause(info.is_pause))
    } else {
      replayObj = this.handleRealReplayType()
    }
    loginCallback && loginCallback(replayObj)
  }
  handleRealReplayType() {
    const { changeScreen, toggleShowWait } = MainAction
    const { dispatch } = this.props
    const info = cloneObj(originData['live'].info)
    const status = info.status || 5
    const allMaterialTime = this.getAllMaterialTime()
    const exceptTime = info.except_time
    const nowTime = getStamp()
    const diff = nowTime - exceptTime
    dispatch(toggleShowWait(false))
    if (status === 5) {
      if (diff < 0) {
        dispatch(changeScreen(-2))
        return {
          type: 'before',
          data: {allMaterialTime, exceptTime}
        }
      } else {
        dispatch(changeScreen(status))
        if (diff < allMaterialTime) {
          return {
            type: 'live',
            data: this.needPlayMaterial(diff)
          }
        } else {
          dispatch(toggleShowWait(true))
        }
      }
    } else {
      dispatch(changeScreen(status))
    }

  }
  needPlayMaterial(diff) {
    const { materials } = originData['live']
    var realDiff, realIndex
    var needDo = []
    const diffObj = this.getMaterialDiffMap()
    for (var key in diffObj) {
      var current = diffObj[key]
      if (diff >= current.start && diff < current.end) {
        realDiff = diff - current.start
        realIndex = key
        break
      }
    }
    if (realDiff >= 0 && realIndex >= 0) {
      const materialMsg = {
        type: Type.COMMON_TYPE.COMMON_LIVE_MATERIAL,
        data: { index: realIndex, time: realDiff },
        seq_time: getSeq(),
        timestamp: getStamp(),
        isDelay: true,
        sender: {}
      }
      needDo.push(materialMsg)
    }
    const remainMaterials = []
    materials.map(function(_, __index) {
      if (__index > realIndex) {
        remainMaterials.push(__index)
      }
    })
    for (var i in remainMaterials) {
      var _index = remainMaterials[i]
      const materialMsg = {
        type: Type.COMMON_TYPE.COMMON_LIVE_MATERIAL,
        data: { index: _index, time: 0 },
        seq_time: getSeq(),
        timestamp: getStamp(),
        isDelay: true,
        sender: {}
      }
      needDo.push(materialMsg)
    }
    return needDo
  }
  getMaterialDiffMap() {
    const { materials } = this.props
    var diffObj = {}
    var stime = 0
    var etime = 0
    materials.map((item, index) => {
      var mtime = this.getMaterialTime(index)
      etime += mtime
      var obj = {
        start: stime,
        end: etime
      }
      diffObj[index] = obj
      stime += mtime
    })
    return diffObj
  }
  getAllMaterialTime() {
    const { materials } = this.props
    var t = 0
    for (var i in materials) {
      t += this.getMaterialTime(i)
    }
    return t
  }
  getMaterialTime(index) {
    const { materials } = this.props
    var current = materials[index]
    if (!current) {
      return 0
    }
    const { info, messages, images } = current
    var time = info.audio_length
    for (var i in messages) {
      var c = formatSocketMsg(messages[i])
      if (c.type === Type.COMMON_TYPE.MATERIAL_START_VIDEO) {
        time += (c.data.video_time * 1000)
      }
    }
    return time
  }
  initQuestion() {
    const { dispatch } = this.props
    const { questions, answers } = originData['live']
    const { initQuestionList } = QuestionAction
    dispatch(initQuestionList({ questions, answers }))
  }
  initDm() {
    const { dispatch } = this.props
    const dm = originData['live'].dm
    const { questions, answers } = originData['live']

    var arr = []
    for (let i in dm) {
      var c = formatSocketMsg(dm[i])
      if (c && !c.data.isSecret) {
        if (c.type === Type.COMMON_TYPE.COMMON_DM_QUESTION) {
          c.data.question = questions.find(_ => _.id === c.data.question_id)
        }
        arr.push(c)
      }
    }
    dispatch(DmAction.initDm(arr))
  }
  initSwiper() {
    const images = originData['live'].images
    const index = this.getCurrnetSwiperIndex()
    const { initSwiper } = liveAction
    const { dispatch } = this.props
    dispatch(initSwiper(images, index))
  }
  getCurrnetSwiperIndex() {
    var currentIndex = 0
    const lastImage = formatSocketMsg(originData['live'].last_image)
    if (lastImage && lastImage.type === Type.COMMON_TYPE.COMMON_LIVE_SLIDE) {
      currentIndex = lastImage.data.index
    }
    return currentIndex
  }
  initQa() {
    const { dispatch } = this.props
    const { faq, questions, answers } = originData['live']
    var arr = []
    for (let i in faq) {
      var c = formatSocketMsg(faq[i])
      if (!c) {
        continue
      }
      if (c.type === Type.COMMON_TYPE.COMMON_QA_QUESTION) {
        let filter = questions.find(r => r.id === c.data.question_id)
        if (!filter) {
          continue
        }
        c.data.question = singleClone(filter)
      } else if (c.type === Type.COMMON_TYPE.COMMON_QA_ANSWER) {
        let filter = answers.find(r => r.id === c.data.answer_id)
        if (!filter) {
          continue
        }
        c.data.answer = filter
        let _filter = questions.find(r => r.id === c.data.answer.question_id)
        if (!_filter) {
          continue
        }
        c.data.question = _filter
      }
      arr.push(c)

    }
    dispatch(QaListAction.initQa(arr))
  }
  clickLoginBtn = () => {
    const { loading, dispatch } = this.props
    if (loading) {
      return
    }
    let value = document.getElementById('htmlCode').innerHTML
    // if (TEST) {
    //   let code = location.search.split('=')[1]
    //   value = code || 9279
    // } else {
    //   value = this.input.value
    // }
    if (value === '') {
      dispatch(LoginAction.changeErrorText('请输入验证码'))
      return
    }
    dispatch(LoginAction.changeErrorText(''))
    dispatch(LoginAction.changeLoading(true))
    //fsQ42O
    MediaManager.prepareMedia(() => {
      this.doLogin(value, TEST)
    })
  }
  async doLogin(code, test) {
    Data.code = code
    Data.test = test
    const { dispatch } = this.props
    var ld = await this.loginPromise(code)
    if (!ld.status) {
      dispatch(LoginAction.changeErrorText(ld.msg))
      dispatch(LoginAction.changeLoading(false))
      return
    }
    GlobalTime.setGlobalTime(ld.data.timestamp)
    dispatch(MainAction.setGlobalToken(ld.data.token))
    if (ld.data.info.status === 15) {
      setData('live', ld.data)
      // originData['live'].info.except_time = getStamp() - 250 * 1000
      Data.user = ld.data.user
      var rd = await this.replayPromise(ld.data)
      if (!rd.status) {
        dispatch(LoginAction.changeErrorText(rd.msg))
        dispatch(LoginAction.changeLoading(false))
        return
      }
      dispatch(LoginAction.changeLoading(false))
      setData('replay', rd.data)
      EventCenter.emit('get_replay_data_success')
      return
    }
    var cd = await this.connectPromise(ld.data.info.id, code, test)
    if (!cd) {
      dispatch(LoginAction.changeErrorText('连接错误，请重试'))
      dispatch(LoginAction.changeLoading(false))
      return
    }
    dispatch(LoginAction.changeLoading(false))
    this.initOriginData(ld.data, code)
  }
  replayPromise(data) {
    const { info, token } = data
    const { id } = info
    return new Promise((resolve, reject) => {
      Request.SendRequest(API.REPLAY_DATA(id, token), 'GET', null, (res) => {
        if (res.status) {
          resolve({
            status: 1,
            data: res.data,
            msg: ''
          })
        } else {
          resolve({
            status: 0,
            data: null,
            msg: res.message || '获取失败,请重试'
          })
        }
      }, (err) => {
        resolve({
          status: 0,
          data: null,
          msg: '获取失败,请重试'
        })
      })
    })
  }
  loginPromise(code) {
    return new Promise((resolve, reject) => {
      Request.SendRequest(API.POST_CODE(code), 'POST', null, (res) => {
        if (res.status) {
          resolve({
            status: 1,
            data: res.data,
            msg: ''
          })
        } else {
          resolve({
            status: 0,
            data: null,
            msg: res.message || '网络错误,请重试'
          })
        }
      }, (err) => {
        resolve({
          status: 0,
          data: null,
          msg: '网络错误,请重试'
        })
      })
    })
  }
  connectPromise(roomId, code, test) {
    return new Promise((resolve, reject) => {
      SocketManager.login({
        code: code,
        roomId: roomId,
        test: test
      }, (bool) => {
        resolve(bool)
      })
    })
  }
  renderBtn() {
    const { loading } = this.props
    const className = loading ? 's_btn loading' : 's_btn'
    return (
      <div className={className} onClick={this.clickLoginBtn}>
        开始观看
        <div className="loading_mask">
          <img className="gif" src={require('../../images/indicator_verybig.gif')} alt="" />
        </div>
      </div>
    )
  }
  renderError() {
    const { error } = this.props
    return (
      <p className="tip">{error}</p>
    )
  }
  handleSubmit = (e) => {
    if (e.keyCode === 13) {
      e.preventDefault();
      this.clickLoginBtn()
    }
  }
  renderInput() {
    const { loading } = this.props
    return (
      <div>
        {this.renderError()}
        {this.renderBtn()}
      </div>
    )
  }
  render() {
    let lessonTitle = document.getElementById('lessonTitle') && document.getElementById('lessonTitle').innerHTML
    let text = this.state.canAuto ? '你好，输入验证码后就可以开始在PC上观看直播' : '很抱歉，safari浏览器不支持音视频自动播放，请使用chrome、火狐、IE等浏览器访问。'
    return (
      <div className="login_screen">
        <div className="__table">
          <div className="__table_cell">
            <div className="login_inner">
              <div className="login_inner_content">
                <div className="tmtm_logo_top">
                  <img className="tntm_logo" src={require('@images/logo-tntm.png')} alt="" />
                  <div className="tntm_title">
                    {lessonTitle}
                  </div>
                </div>

                <div className="line" style={{marginTop: 0}}></div>
                { this.renderInput() }
              </div>
            </div>
          </div>
        </div>
      </div>
    )
  }
}
const mapStateToProps = (state) => {
  return Object.assign({}, state.LoginState, {
    materials: state.MainScreenState.materials
  })
}

export default connect(mapStateToProps)(SilentLogin)
